﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace FoundationLib.Ifc.DependencyInjection
{
	/// <summary>
	/// Provides access to a dependency injection container.
	/// </summary>
	public interface IIocContainer : IDisposable
	{
		/// <summary>
		/// Initialises the container.
		/// </summary>
		void Initialise();

		/// <summary>
		/// Resolves an instance of the specified type and returns it.
		/// </summary>
		/// <typeparam name="T">The type</typeparam>
		/// <returns>The instance of type <typeparamref name="T"/></returns>
		T Resolve<T>();

		/// <summary>
		/// Resolves an instance of the specified type and returns it.
		/// </summary>
		/// <typeparam name="T">The type</typeparam>
		/// <param name="key">The key</param>
		/// <returns>The instance of type <typeparamref name="T"/></returns>
		T Resolve<T>(string key);

		/// <summary>
		/// Resolves an instance of the specified type and returns it.
		/// </summary>
		/// <param name="arguments">Arguments to be passed when creating the instance</param>
		/// <typeparam name="T">The type</typeparam>
		/// <returns>The instance of type <typeparamref name="T"/></returns>
		T Resolve<T>(object arguments);

		/// <summary>
		/// Resolves an instance of the specified type and returns it.
		/// </summary>
		/// <param name="key">The key</param>
		/// <param name="arguments">Arguments to be passed when creating the instance</param>
		/// <typeparam name="T">The type</typeparam>
		/// <returns>The instance of type <typeparamref name="T"/></returns>
		T Resolve<T>(string key, object arguments);

		/// <summary>
		/// Resolves all instances of the specified type and returns them.
		/// </summary>
		/// <typeparam name="T">The type</typeparam>
		/// <returns>The instances of type <typeparamref name="T"/></returns>
		T[] ResolveAll<T>();

		/// <summary>
		/// Resolves all instances of the specified type and returns them.
		/// </summary>
		/// <typeparam name="T">The type</typeparam>
		/// <param name="arguments">Arguments to be passed when creating the instances</param>
		/// <returns>The instances of type <typeparamref name="T"/></returns>
		T[] ResolveAll<T>(object arguments);
	}
}
